local forbidden = { "crane_frame", "oildrum001_explosive.mdl","sawblade001a.mdl" ,"bombercheap","crane_body_LOD",
"crane_docks","CollapsedBuilding","project_building","project_destroyedbuildings","row_church_fullscale",
"row_corner","row_hill_cluster","row_industrial_cluster","row_res_","row_upscale","short_building","watertower",
"utilitypole01d","canal_bridge01","canal_bridge01b","canal_bridge02","canal_bridge03a","canal_bridge03b",
"canal_bridge03c","canal_bridge04","refinery_03","refinery_04","refinery_05","citadel","evildisc_corp.mdl",
"amraam","mk-82","facepunch_logo","ww2bomb","torpedo","tower.mdl","road_curve","road_long","road_medium","road_short","cannonball.mdl",
"flakshell_big.mdl"}

function GM:InitPostEntity( )
local Entities = ents.GetAll()
	for _, ent in pairs (Entities) do
		local entid = ent:EntIndex() 
		servertable["entitys"][entid] = {}
		servertable["entitys"][entid]["owner"] = "Map"
	end
Msg("Registerd " ..table.getn( Entities ) .. " Map-owned Entities \n")
end 

function GetOwnStatus(plyuni,ent)
	local entid = ent:EntIndex() 
	if servertable["entitys"][entid] then
		if (servertable["entitys"][entid]["owner"] == plyuni) then
			return 1
		else
			return 3
		end
	else
		return 2
	end
end

function IsOwner(ent,ply)
	if (GetOwnStatus(ply:UniqueID(),ent) == 1) then 
		return true
	else 
		return false
	end
end

function SpawnedProp( ply, Path, ent ) 
	local plyuni = ply:UniqueID()
	ply.nextspawnprop = CurTime( ) + 1
	local class = ent:GetClass()
	ent:GetPhysicsObject():EnableGravity( false ) 
	ent:GetPhysicsObject():EnableDrag( false )	
	servertable["entitys"][ent:EntIndex()] = {}
	servertable["entitys"][ent:EntIndex()]["owner"] = plyuni
	Checklimit(ply,class,ent)
	servertable["ply"][plyuni]["ShipRegisterd"] = false
end
hook.Add( "PlayerSpawnedProp", "playerSpawnedProp", SpawnedProp );  
hook.Add("PlayerSpawnedEffect", "playerSpawnedEffect", SpawnedProp)

function SpawnedSENT( userid, propid ) 
SpawnedProp(userid,nil,propid)
end
hook.Add( "PlayerSpawnedSENT", "playerSpawnedSENT", SpawnedSENT );

function Checklimit (ply,entityclass,entspawned)
	local plyuni = ply:UniqueID()
	local allowedamount = 0
	for k, entclass in pairs (servertable["ply"][plyuni]["count"]["own"]["owns"]) do
		if (entclass == entityclass) then
			allowedamount = tonumber(servertable["ply"][plyuni]["count"]["own"]["ownamount"][k])
		end
	end
	local amount = GetClassCount(entityclass,ply,entspawned)	
	if not (allowedamount >= amount) then
		ply:SendLua("GAMEMODE:AddNotify(\"" ..  "You hit your " .. Translate(entityclass) .. " limit" .. "\", " .. "NOTIFY_ERROR" .. ", 5); surface.PlaySound( \"" .. "buttons/button2.wav" .. "\" )")
		if entspawned then
			entspawned:Remove()
		end
	else
	end
	if (entityclass == "Test") then
		if GetClassCount("Test2",ply,entspawned) > 1 then
			entspawned:Remove()
			ply:SendLua("GAMEMODE:AddNotify(\"" ..  "Only one type allowed" .. "\", " .. "NOTIFY_ERROR" .. ", 5); surface.PlaySound( \"" .. "buttons/button2.wav" .. "\" )")
		end
	end
	if (entityclass == "Test2") then
		if (GetClassCount("Test",ply,entspawned) > 1) then
			entspawned:Remove()
			ply:SendLua("GAMEMODE:AddNotify(\"" ..  "Only one type allowed" .. "\", " .. "NOTIFY_ERROR" .. ", 5); surface.PlaySound( \"" .. "buttons/button2.wav" .. "\" )")
		end
	end
end

function GetClassCount(class,ply,entspawned)
	local amount = 1
	for index, ent in ipairs(ents:GetAll()) do 
		if (entspawned != ent) then
			if (ent:GetClass() == 	class) then
				if IsOwner(ent,ply) then
					amount = amount +1
				end
			end
		end
	end
	return amount
end

function getshipcore(ent)
	if ent:IsValid() then
		if servertable["entitys"][ent:EntIndex()] then
			local owner = servertable["entitys"][ent:EntIndex()]["owner"]
			for k,core in pairs(constraint.GetAllConstrainedEntities( ent )) do 
				if core:IsValid() then
					if (core:GetClass() == "Shipcore") then
						if (servertable["entitys"][core:EntIndex()]["owner"] == owner) then
							return core
						end
					end
				end
			end
		end
	end
	return nil
end

function getcargo(ent)
	if ent:IsValid() then
		if servertable["entitys"][ent:EntIndex()] then
			local owner = servertable["entitys"][ent:EntIndex()]["owner"]
			for k,core in pairs(constraint.GetAllConstrainedEntities( ent )) do 
				if core:IsValid() then
					if (core:GetClass() == "cargo") then
						if (servertable["entitys"][core:EntIndex()]["owner"] == owner) then
							return core
						end
					end
				end
			end
		end
	end
	return nil
end

function Removeremovetimer( ply ) 
	local name = "Removetimer" .. ply:UniqueID( )
	if (timer.IsTimer(name)) then
		timer.Destroy(name)
	end
	Msg ("Stop Removetimer for " .. ply:GetName() .. "\n")
end 
hook.Add( "PlayerInitialSpawn", "Removeremovetimer", Removeremovetimer );

function Removeit(ply)
	local players = player.GetAll( )
	for _, ply2 in pairs( players ) do  
		ply2:PrintMessage(HUD_PRINTTALK, ply:GetName( ) .. " Disconnected, will delete his Stuff in 10Minutes \n")
	end	
	Msg ("Deleting ".. ply:GetName( ) .. "'s stuff in ".. 120 .. " seconds \n")
	local name = "Removetimer" .. ply:UniqueID( )
	timer.Create(name,120, 1, Removeitreally, ply:UniqueID( )) 
end
hook.Add( "PlayerDisconnected", "Removestuff", Removeit )  

function Removeitreally(id)
	for _, entid in pairs(servertable["entitys"]) do  
		local ent = Entity(entid)
		if ent:IsValid() then
			if servertable["entitys"][entid]["owner"] == id then
				ent:Remove()
			end
		end
	end
end

function UseTool( pl, tr, toolmode ) 
	local plyuni = pl:UniqueID()
	servertable["ply"][plyuni]["ShipRegisterd"] = false
	if (toolmode == "adv_duplicator") then
		if (InBuildZone(tr.HitPos)) then
			return true
		end
    end
	if (tr.Entity) then
		if (GetOwnStatus(plyuni,tr.Entity) == 1) then
			return true 
		end
        pl:PrintMessage(HUD_PRINTCENTER, "Not your Stuff!" ) return false
    end
    return false
end 
hook.Add( "CanTool", "Toolguncheck", UseTool );  

function GravGunCheck( pl, tr) 
	if UseTool(pl, tr) then
		return
	else
		return false
	end
end
hook.Add("GravGunPickupAllowed", "GravGunCheck", GravGunCheck);  

function UsePhysgun( pl, tr, toolmode ) 
	local plyuni = pl:UniqueID()
	if (tr.Entity) then
		if (tr.Entity:IsValid()) then
			if(tr.Entity:IsPlayer()) then return false end
			if (InBuildZone(tr.Entity:GetPos( )) ) then
				if (InBuildZone(pl:GetPos( )) ) then
					if (tr.Entity) then
						if (GetOwnStatus(plyuni,tr.Entity) == 1) then
		                    return true 
				        end
				        pl:PrintMessage(HUD_PRINTCENTER, "Not your Stuff!" ) return false
				    end
				else
					pl:PrintMessage(HUD_PRINTCENTER, "No BuildZone" )
				end
			else
				pl:PrintMessage(HUD_PRINTCENTER, "No BuildZone" )
			end
		end
		return false
	end
end
hook.Add( "PhysgunPickup", "physguncheck", UsePhysgun );  

function blockProps( ply, mdl ) 
 	if not (InBuildZone(ply:GetPos( )) ) then ply:PrintMessage(HUD_PRINTCENTER, "Not in Buildzone" )
	return false end
	if (CurTime( ) < ply.nextspawnprop) then 	ply:PrintMessage(HUD_PRINTCENTER, "Stop Spamming, Asshole" ) return false end  --preventspamming
	for _, v in pairs( forbidden ) do 
		if string.find( mdl, v ) then 
			ply:SendLua("GAMEMODE:AddNotify(\"" .. "This Model: " .. mdl .. " is forbidden" .. "\", " .. "NOTIFY_ERROR" .. ", 5); surface.PlaySound( \"" .. "buttons/button2.wav" .. "\" )")
			return false 
		end 
	end
end 
hook.Add( "PlayerSpawnProp", "blockProps", blockProps )  
hook.Add("PlayerSpawnEffect", "blockeffects", blockProps)  

function PlayerSpawnVehicle(ply) 
	ply:PrintMessage(HUD_PRINTCENTER, "Use the Freelancer Capsule under Entitys" )
	return false
end
hook.Add( "PlayerSpawnVehicle", "PlayerSpawnVehicle", PlayerSpawnVehicle );  
hook.Add( "PlayerSpawnRagdoll", "PlayerSpawnRagdoll", PlayerSpawnVehicle );  

function NPCSpawn(ply) 
	ply:PrintMessage(HUD_PRINTCENTER, "Of course you are not allowed to spawn NPC's" )
	return false
end 
hook.Add( "PlayerSpawnNPC", "playerSpawnNPCTest", NPCSpawn ); 

function gravgunPunt(userid) 
	userid:PrintMessage(HUD_PRINTCENTER, "No Punting allowed" )
	return false
end 
hook.Add( "GravGunPunt", "gravgunPunt", gravgunPunt ); 

function SWEPSpawn( ply, cmd, args )
    ply:PrintMessage(HUD_PRINTCENTER, "You need ro buy weapons" )
	return false;
end
concommand.Add( "gm_giveswep", SWEPSpawn ); 
